home *** CD-ROM | disk | FTP | other *** search
/ SGI Hot Mix 17 / Hot Mix 17.iso / HM17_SGI / research / lib / read_gif.pro < prev    next >
Text File  |  1997-07-08  |  6KB  |  230 lines

  1. ; $Id: read_gif.pro,v 1.8 1997/03/12 20:52:36 stevep Exp $
  2. ;
  3. ; Copyright (c) 1992-1997, Research Systems, Inc.  All rights reserved.
  4. ;       Unauthorized reproduction prohibited.
  5.  
  6. ;
  7. ;  GifReadByte
  8. ;    Read a single byte out of the given file
  9. ;
  10. FUNCTION GifReadByte, unit
  11.     ch    = 0b
  12.     READU, unit, ch
  13.     RETURN, ch
  14. END
  15.  
  16. PRO READ_GIF, FILE, IMAGE, R, G, B, MULTIPLE=mult, CLOSE=close
  17. ;
  18. ;+
  19. ; NAME:
  20. ;    READ_GIF
  21. ;
  22. ; PURPOSE:
  23. ;    Read the contents of a GIF format image file and return the image
  24. ;    and color table vectors (if present) in the form of IDL variables.
  25. ;
  26. ; CATEGORY:
  27. ;    Input/Output.
  28. ;
  29. ; CALLING SEQUENCE:
  30. ;    READ_GIF, File, Image [, R, G, B]
  31. ;
  32. ; INPUTS:
  33. ;    File:    Scalar string giving the name of the rasterfile to read
  34. ;
  35. ; Keyword Inputs:
  36. ;    CLOSE = if set, closes any open file and returns if the MULTIPLE images
  37. ;        per file mode was used.  This keyword is used
  38. ;        without additional parameters.
  39. ;    
  40. ;    MULTIPLE = if set, read files containing multiple images per
  41. ;        file.  Each call to READ_GIF returns the next image,
  42. ;        with the file remaining open between calls.  The File
  43. ;        parameter is ignored after the first call.  Reading
  44. ;        past the last image returns a scalar value of -1 in IMAGE, and
  45. ;        closes the file.  When reading the 2nd and subsequent
  46. ;        images, R, G, and B are not returned.
  47. ;
  48. ; OUTPUTS:
  49. ;    Image:    The 2D byte array to contain the image.
  50. ;
  51. ;
  52. ; OPTIONAL OUTPUT PARAMETERS:
  53. ;     R, G, B:    The variables to contain the Red, Green, and Blue color vectors
  54. ;        if the rasterfile containes colormaps.
  55. ;
  56. ; SIDE EFFECTS:
  57. ;    None.
  58. ;
  59. ; COMMON BLOCKS:
  60. ;    READ_GIF_COMMON.
  61. ; RESTRICTIONS:
  62. ;    This routine only reads in the first image in a file (the format
  63. ;    allows many). Local colormaps are not supported.
  64. ;    Only 8 bit images are supported.
  65. ;
  66. ;    The Graphics Interchange Format(c) is the Copyright property
  67. ;    of CompuServ Incorporated.  GIF(sm) is a Service Mark property of
  68. ;    CompuServ Incorporated. 
  69. ;
  70. ; EXAMPLE:
  71. ;    To open and read the GIF image file named "foo.gif" in the current
  72. ;    directory, store the image in the variable IMAGE1, and store the color
  73. ;    vectors in the variables R, G, and B, enter:
  74. ;
  75. ;        READ_GIF, "foo.gif", IMAGE1, R, G, B
  76. ;
  77. ;    To load the new color table and display the image, enter:
  78. ;
  79. ;        TVLCT, R, G, B
  80. ;        TV, IMAGE1
  81. ; MODIFICATION HISTORY:
  82. ;    Written June 1992, JWG
  83. ;    Added GIF89a and interlaced format, Jan, 1995, DMS.
  84. ;    Added MULTIPLE and CLOSE, Aug, 1996.
  85. ;    
  86. ;-
  87. ; Copyright (c) 1992-1996, Research Systems, Inc.  All rights reserved.
  88. ;    Unauthorized reproduction prohibited.
  89. ;
  90.  
  91. ;    Define GIF header (and screen descriptor)
  92.  
  93. COMMON READ_GIF_COMMON, unit, width, height
  94.  
  95. if n_elements(unit) eq 0 then unit = -1
  96.  
  97.  
  98. on_error, 2        ;Return to caller on errors
  99. image  = -1        ;No image read yet
  100.  
  101. if keyword_set(close) then begin
  102.     if unit gt 0 then FREE_LUN, unit
  103.     unit = -1
  104.     return
  105.     endif
  106.  
  107. h    = {     magic:bytarr(6),                $
  108.         width_lo:0b, width_hi:0b,            $
  109.         height_lo:0b, height_hi:0b,            $
  110.         screen_info:0b, background:0b, reserved:0b }
  111.  
  112. ;    Image header declaration
  113.  
  114. ihdr    = {     left:0, top:0,            $    ; we read this but
  115.         iwidth:0, iheight:0,        $    ; mostly we ignore
  116.         image_info:0b }                ; its content
  117.  
  118. if keyword_set(mult) and unit gt 0 then goto, next_image
  119. if unit gt 0 then free_lun, unit
  120.  
  121. OPENR, unit, file, /GET_LUN, /BLOCK, ERROR=i
  122. if i ne 0 then message, 'Error occured opening file: '+file+'.'
  123.  
  124. READU, unit, h        ;Read gif header
  125.  
  126. ;    Check Magic in header: GIF87a or GIF89a.
  127. gif    = STRING(h.magic[0:2])
  128. vers = STRING(h.magic[3:5])
  129.  
  130. IF gif NE 'GIF' THEN BEGIN
  131.     FREE_LUN, unit
  132.     unit = -1
  133.     MESSAGE, 'File ' + file + ' is not a GIF file.'
  134. ENDIF
  135.  
  136. IF vers ne '87a' and vers ne '89a' then $
  137.     MESSAGE, /INFO, 'GIF Version incompatible:'+vers+'.'
  138.  
  139. width    = h.width_hi * 256 + h.width_lo
  140. height    = h.height_hi * 256 + h.height_lo
  141.  
  142. ;    Find out how big the color map is
  143.  
  144. bits_per_pixel    = (h.screen_info AND 'F'X) + 1
  145. color_map_size    = 2 ^ bits_per_pixel
  146.  
  147. ;    Read in the colormap (optional)
  148.  
  149. IF (h.screen_info AND '80'X) NE 0 THEN BEGIN
  150.     map    = BYTARR(3,color_map_size, /NOZERO)
  151.     READU, unit, map
  152.     map    = transpose(map)
  153.     r    = map[*,0]
  154.     g    = map[*,1]
  155.     b    = map[*,2]
  156.     ENDIF
  157.  
  158.  
  159. ;    Read the image description
  160.  
  161. next_image:  while 1 do begin        ;Read till we get a terminator
  162.   cmd = GifReadByte(unit)        ;Loop thru commands in file.
  163.   CASE STRING(cmd) OF
  164.  
  165. ';':    BEGIN                ; GIF trailer (0x3b)
  166.     FREE_LUN, unit
  167.     unit = -1
  168.     return
  169.     ENDCASE
  170.  
  171. ',':    BEGIN                ; Image description (0x2c)
  172.     READU,unit,ihdr
  173.  
  174.     ; Check for file formats we don't support
  175.     ; We don't support local colormaps
  176.  
  177.     if (ihdr.image_info AND '80'X) NE 0 THEN begin  ;Local color map
  178.        lcolor_map_size = 2^((ihdr.image_info and 7) + 1)
  179.        junk = bytarr(3, lcolor_map_size, /NOZERO)
  180.        readu, unit, junk
  181.        message,'Local colormaps ignored.', /CONTINUE
  182.        endif
  183.  
  184.     ;    Allocate an array to hold the image
  185.     image    = BYTARR(width, height, /NOZERO)
  186.  
  187.     ;    Now call special GIF-LZW routine hidden within IDL
  188.     ;    to do the ugly serial bit stream decoding
  189.  
  190.     DECODE_GIF,unit,image        ; magic
  191. ;        This should be the 0 byte that ends the series:
  192.     dummy = GifReadByte(unit)    ;Loop thru commands in file.
  193.     if dummy ne 0 then message,/info,'No trailing 0.'
  194.  
  195.     ;    Reorder rows in an interlaced image
  196.  
  197.     if (ihdr.image_info AND '40'X) NE 0 THEN BEGIN
  198.         l = lindgen(height)    ;Row indices...
  199.             ;Giff interlace ordering
  200.         p = [l[where(l mod 8 eq 0)], l[where(l mod 8 eq 4)], $
  201.          l[where(l mod 4 eq 2)], l[where(l and 1)]]
  202.         image2 = bytarr(width, height, /NOZERO)
  203.         h1 = height-1
  204.         for i=0, h1 do image2[0, h1-p[i]] = image[*,h1-i]
  205.         image = temporary(image2)
  206.     ENDIF
  207.     if keyword_set(mult) then return    ;Leave file open
  208.         FREE_LUN, unit
  209.         unit = -1
  210.         RETURN
  211.     ENDCASE
  212.  
  213. '!':    BEGIN                ;Gif Extention block (ignored) (0x21)
  214.     label = GifReadByte(unit)    ;toss extension block label
  215.     repeat begin            ;read and ignore blkss
  216.       blk_size = GifReadByte(unit)    ;block size
  217.       if blk_size ne 0 then begin
  218.         junk = BYTARR(blk_size, /NOZERO)
  219.         READU, unit, junk
  220.         endif
  221.     endrep until blk_size eq 0
  222.     ENDCASE
  223.  
  224. ELSE:    message,'Unknown GIF keyword in ' + file + string(cmd, format='(2x,Z2)')
  225. ENDCASE
  226. endwhile
  227.  
  228. END
  229.